
def analyze_frame_times(times, refresh_rate=60):
    """
    Opens a plot displaying information about the frame times passed.
    Inputs:
        times           : A list of frame times in seconds.
        refresh_rate=60 : the refresh rate of the display device, used to
                          determine what long frame times means.
    Returns:
        None
    """
    import pylab
    
    one_frame_time = 1.0/(refresh_rate*1.0)
    tol = 0.1 * one_frame_time # 10 percent
    # go through and categorize timings
    very_long_frames = dict()
    long_frames = dict()
    for i in xrange(len(times)-1): 
        dt = times[i+1] - times[i]
        if dt >= 2*one_frame_time + tol:
            very_long_frames[i] = dt
        elif dt >= one_frame_time + tol:
            long_frames[i] = dt
        elif dt < one_frame_time + tol:
            pass # a normal frame requires no action

    # plot the long_frames and very_long frames x=frame_no y=dt
    pylab.figure()
    # very long frames
    very_long_frame_time = [times[i] for i in very_long_frames.keys()]
    very_long_frame_dt = [very_long_frames[i]*1000 for i in very_long_frames.keys()]
    pylab.plot(very_long_frame_time, very_long_frame_dt, 'ro')

    # long frames
    long_frame_time = [times[i] for i in long_frames.keys()]
    long_frame_dt = [long_frames[i]*1000 for i in long_frames.keys()]
    pylab.plot(long_frame_time, long_frame_dt, 'bo')

    pylab.xlim( (0,times[-1]) )
    pylab.title("Frame Duration Analysis \n%d long frames (%3.3f %s), %d very long frames (%3.3f %s), %d frames" % 
                (len(long_frame_time), 100.0*len(long_frame_time)/(len(times)*1.0),'%',
                len(very_long_frame_time), 100.0*len(very_long_frame_time)/(len(times)*1.0), '%',
                len(times) ) )
    pylab.xlabel( "Time (seconds)    Total=%3.4f" % times[-1] )
    pylab.ylabel( "Frame Duration (ms)" )

    pylab.show() 
